package com.jkozniewski.geom
{
	import flash.geom.Point;
	
	// r = x * cos(teta) + y * sin(teta)	
	public class Line
	{
		private var _A:Number,_B:Number,_C:Number,_T:Number;
		
		public function Line(a:Number, b:Number, c:Number, t:Number) { _A = a; _B = b; _C = c; _T = t; }
		public static function getLine(x1:Number, y1:Number, x2:Number, y2:Number):Line
		{
			var t:Number = Math.atan2(-x2+x1, y2-y1);
			//trace(t/Math.PI*180);
			//t = (t+ Math.PI) %(Math.PI);
			//trace(t/Math.PI*180);
			var a:Number = Math.cos(t);
			var b:Number = Math.sin(t);
			var c:Number = x1*a + y1*b;
			return new Line(a,b,c,t);
		}
		public function getIntersect(l:Line):Point
		{
			if(_A==0) return null;
			
			var y:Number = ( _A * l.C - l.A * _C) / (l.B * _A - l.A * _B);
			var x:Number = (_C - _B * y)/_A;
			
			return new Point(x, y);
		}
		public function mirrorPoint(p:Point):Point
		{
			var _A2:Number = -_B; // cos(90+teta) = -sin(teta);
			var _B2:Number = _A; // sin(90+teta) = cos(teta);
			var _C2:Number = _A2 * p.x + _B2 * p.y;
			var _DET:Number = _A*_B2 - _A2*_B;
			var x:Number = (_B2*_C - _B*_C2) / _DET;
			var y:Number = (_C2 - x*_A2) / _B2;
			x+= x-p.x;
			y+= y-p.y;
			return new Point(x,y);
		}
		public function getPerpLine(p:Point):Line { //felezomeroleges
			var _A2:Number = -_B; // cos(90+teta) = -sin(teta);
			var _B2:Number = _A; // sin(90+teta) = cos(teta);
			var _C2:Number = _A2 * p.x + _B2 * p.y;
			return new Line(_A2, _B2, _C2, _T+Math.PI/2);
		}
		public function getBisectorLines(line:Line):Array
		{
			var inter:Point = this.getIntersect(line);
			
			var t1:Number = (T + line.T + Math.PI)/2;
			var a1:Number = Math.cos(t1);
			var b1:Number = Math.sin(t1);
			var c1:Number = inter.x*a1 + inter.y*b1;
			var line1:Line = new Line(a1,b1,c1,t1);
			
			var t2:Number = (T + line.T)/2;
			var a2:Number = Math.cos(t2);
			var b2:Number = Math.sin(t2);
			var c2:Number = inter.x*a2 + inter.y*b2;
			var line2:Line = new Line(a2,b2,c2,t2);
			return [line1, line2];
		}
		public function getPointByX(x:Number):Point { return new Point(x, (_C - x*_A)/_B); }
		public function getPointByY(y:Number):Point { return new Point((_C - y*_B)/_A, y); }
		public function get A():Number { return _A; }
		public function get B():Number { return _B; }
		public function get C():Number { return _C; }
		public function get T():Number { return _T; }
	}
}